<template>
	<view class="main">
		<view class="map-box">
			<view class="map-content">
				<Map
					type="addTask"
					:taskZone="zoneList"
					:mapUrl="mapUrl"
					:TaskPathList="taskPathList" />
			</view>
		</view>
	</view>
	<view class="task-box">
		<view class="line-box">
			<up-line length="37" height="0.6vh"></up-line>
		</view>
		<view class="tilte-box">
			<view class="but">
				<up-text
					:text="t('plan.type')"
					color="#0084fc"
					bold
					size="14"></up-text>
				<up-tooltip
					v-if="!isEdit"
					triggerMode="click"
					direction="top"
					zIndex="999"
					bgColor="#303133">
					<template #trigger>
						<up-icon
							name="question-circle"
							class="icon"
							color="#999999"
							size="14"></up-icon>
					</template>
					<template #content>
						<up-text
							:text="t('plan.changeSequence')"
							color="#fff"
							class="tip"
							size="12"></up-text>
					</template>
				</up-tooltip>
			</view>
			<view class="but" v-if="!isEditSingle && !hasDetailInfo">
				<up-button
					text="返回"
					@click="returnFun"
					v-if="!isEdit"></up-button>
				<up-button
					text="完成"
					@click="isEdit ? saveFun(0) : saveFun(1)"></up-button>
			</view>
		</view>
		<scroll-view class="task-list-com" v-if="isEdit" scroll-y>
			<view class="task-list" v-for="(item, index) in taskList">
				<singleChoiceVue
					width="50%"
					:list="state.typeList"
					:defaultVal="item.type"
					:Listindex="index"
					:disabled="hasDetailInfo"
					@changeVal="changeTypeVal" />
				<view class="choseZone" v-if="item.type == 'zone'">
					<up-button @click="!hasDetailInfo ? (showZone = true) : ''">
						{{ item.zoneVal[0] || "请选择分区" }}
					</up-button>
				</view>
				<up-picker
					v-if="item.type == 'zone'"
					:show="showZone"
					v-model="item.zoneVal"
					placeholder="请选择分区"
					@confirm="confirmZone"
					@cancel="confirmZone"
					@close="confirmZone"
					confirmText="完成"
					:columns="state.defaultZone"
					keyName="zone_name"
					valueName="id"
					closeOnClickOverlay></up-picker>
				<up-picker
					v-model="item.pathVal"
					:hasInput="true"
					v-if="item.type == 'path'"
					placeholder="请选择路径"
					confirmText="完成"
					:columns="state.defaultPath"
					:disabled="hasDetailInfo"
					@confirm="confirmPath"
					keyName="path_name"
					valueName="id"
					closeOnClickOverlay></up-picker>
				<view class="but-box" v-if="item.type == 'zone'">
					<up-button
						v-for="(i, ind) in state.butList"
						:text="i.name"
						:class="item.task_type == i.value ? 'active-but' : ''"
						:key="ind"
						:disabled="hasDetailInfo"
						@click="changeZoneType(index, i.value)"></up-button>
				</view>
				<up-text
					:text="t('plan.strength')"
					color="#666666"
					bold
					size="14"></up-text>
				<singleChoiceVue
					:list="state.modeList"
					:disabled="hasDetailInfo"
					:defaultVal="item.rub_type"
					:Listindex="index"
					@changeVal="changeMadeVal" />
				<up-text
					:text="t('plan.speed')"
					color="#666666"
					bold
					size="14"></up-text>
				<singleChoiceVue
					:list="state.speedList"
					:disabled="hasDetailInfo"
					:defaultVal="item.max_speed"
					:Listindex="index"
					@changeVal="changeSpeedVal" />
				<view class="open">
					<up-text
						:text="t('plan.brush')"
						color="#666666"
						bold
						size="14"></up-text>
					<up-switch
						v-model="item.brush"
						size="22"
						:disabled="hasDetailInfo"></up-switch>
				</view>
				<view class="open" v-if="modelId === 'YZYH'">
					<up-text
						:text="t('plan.atomization')"
						color="#666666"
						bold
						size="14"></up-text>
					<up-switch
						v-model="item.water"
						size="22"
						:disabled="hasDetailInfo"></up-switch>
				</view>
				<view class="open" v-if="modelId === 'YZYH'">
					<up-text
						:text="t('plan.patrol')"
						color="#666666"
						bold
						size="14"></up-text>
					<up-switch
						v-model="item.patrol"
						size="22"
						:disabled="hasDetailInfo"></up-switch>
				</view>
				<up-text
					:text="t('addPlan.cycle')"
					color="#666666"
					bold
					size="14"></up-text>
				<view class="num-box">
					<up-number-box
						:min="1"
						:max="10"
						:disabled="hasDetailInfo"
						v-model="item.task_times"></up-number-box>
				</view>
				<view class="open-edg" v-if="item.type == 'path'">
					<up-text
						:text="t('addPlan.strongEdge')"
						color="#666666"
						bold
						size="14"></up-text>
					<up-switch
						v-model="item.isopens"
						size="22"
						:disabled="hasDetailInfo"></up-switch>
				</view>
				<up-line color="#f5f6f7" class="line-bottm"></up-line>
			</view>
			<view class="last-but" v-if="!hasDetailInfo">
				<up-button
					text="继续添加"
					@click="addTaskFun"
					v-if="!isEditSingle"></up-button>
				<up-button
					text="返回"
					@click="cancelEditSingle"
					v-if="isEditSingle"></up-button>
			</view>
		</scroll-view>
		<view v-if="!isEdit && taskList.length" class="drag-box">
			<up-swipe-action>
				<up-dragsort
					:initialList="taskList"
					direction="vertical"
					@drag-end="onVerticalDragEnd">
					<template #default="{ item, index }">
						<up-swipe-action-item
							:options="state.options"
							@click="operateClick($event, item, index)">
							<view class="drag-item">
								<text>
									{{
										item.type == "zone"
											? item.zoneVal[0]
											: item.pathVal[0]
									}}
								</text>
								<up-avatar
									shape="square"
									size="22"
									src="/static/image/device/dot.png"></up-avatar>
							</view>
						</up-swipe-action-item>
					</template>
				</up-dragsort>
			</up-swipe-action>
		</view>
		<u-modal
			:show="showTip"
			:show-cancel-button="true"
			:cancel-text="t('cancel')"
			:confirm-text="t('sure')"
			contentTextAlign="center"
			@confirm="handleConfirm"
			@cancel="handleCancel"
			cancelColor="#333"
			confirmColor="#007aff">
			<template v-slot>
				<view class="content">
					<view class="title">
						<text class="blackTip">
							{{ t("plan.taskName") }}
						</text>
					</view>
					<up-input
						v-model="inputValue"
						:placeholder="t('plan.inputName')"
						:custom-style="inputStyle"
						@focus="isFocused = true"
						@blur="isFocused = false"></up-input>
				</view>
			</template>
		</u-modal>
	</view>
</template>

<script setup lang="ts">
import Map from "@/components/Map/index.vue";
import { cloneDeep, isEqual } from "lodash-es";
import singleChoiceVue from "./singleChoice.vue";
import { useDeviceStore } from "@/stores/device";
import {
	reactive,
	ref,
	watch,
	onMounted,
	getCurrentInstance,
	nextTick,
	computed,
} from "vue";
import { createPlan } from "@/service/index";
import { useI18n } from "vue-i18n";
const { t } = useI18n();
const props = defineProps<{
	device_sn: string;
	mapUrl: string;
	detailInfo?: Plan;
}>();
const instance: any = getCurrentInstance();
const deviceStore = useDeviceStore();
const zoneList = ref<ZoneDisplay[]>([]);
const taskPathList = ref<PathItem[]>([]);
const defaultDevice = useUniversalStorage("DefaultDevice", {});
const taskList = ref<tasks[]>([]);
const taskListSave = ref<tasks[]>([]);
const showZone = ref(false);
const modelId = ref("");
const isEdit = ref(true);
const isEditSingle = ref(false);
const editIndex = ref(0);
const mapId = ref("");
const showTip = ref(false);
const inputValue = ref("");
const isFocused = ref(false);
// 初始化时保存原始副本
const initialTaskList = ref<tasks[]>([]);
const isModified = ref(false);
const emit = defineEmits(["isSave"]);
const hasDetailInfo = computed(() => !!props.detailInfo);
// 深度监听变化
watch(
	taskList,
	(newVal) => {
		if (initialTaskList.value.length) {
			isModified.value = !isEqual(newVal, initialTaskList.value);
			emit("isSave", isModified.value);
		}
	},
	{ deep: true }
);
// 动态计算样式
const inputStyle = computed(() => ({
	border: isFocused.value
		? "2px solid #e59700 !important"
		: "1px solid #eee !important",
}));
const state = reactive({
	options: [
		{
			text: "编辑",
			style: {
				backgroundColor: "rgb(0, 82, 217)",
			},
		},
		{
			text: "删除",
			style: {
				backgroundColor: "rgb(227, 77, 89)",
			},
		},
	],
	typeList: [
		{
			name: "分区",
			value: "zone",
		},
		{
			name: "路径",
			value: "path",
		},
	],
	butList: [
		{
			name: "沿边",
			value: "edge",
		},
		{
			name: "覆盖",
			value: "coverage",
		},
		{
			name: "沿边+覆盖",
			value: "both1",
		},
		{
			name: "覆盖+沿边",
			value: "both2",
		},
	],
	modeList: [
		{
			name: "自动",
			value: "huge",
		},
		{
			name: "小",
			value: "small",
		},
		{
			name: "中",
			value: "median",
		},
		{
			name: "大",
			value: "big",
		},
	],
	speedList: [
		{
			name: "0.5m/s",
			value: 0.5,
		},
		{
			name: "0.7m/s",
			value: 0.7,
		},
		{
			name: "1.0m/s",
			value: 1,
		},
	],
	defaultZone: <ZoneDisplay[]>[],
	defaultPath: <PathItem[]>[],
});
const onVerticalDragEnd = (list: tasks[]) => {
	taskList.value = list;
	getPaths();
};

const handleConfirm = async () => {
	const processedTasks = processTaskTypes(taskList.value);
	// 2. 构建请求参数
	const params: PlanParams = {
		device_sn: props.device_sn,
		map_id: mapId.value,
		plan_desc: inputValue.value,
		tasks: processedTasks,
	};
	// 3. 发送请求
	const res = await createPlan(params);
	if (res.data.code === 0) {
		instance.proxy.$message(t("saveOk"), "success");
		const pages = getCurrentPages();
		if (pages.length >= 2) {
			uni.navigateBack({ delta: 1 });
		} else {
			// 降级方案：跳转到指定页面
			uni.redirectTo({
				url: `/pages/manage/cleaningTask/index?device_sn=${props.device_sn}`,
			});
		}
	} else {
		showTip.value = false;
		instance.proxy.$message(t("data.msg"), "warning");
	}
};
const handleCancel = () => {
	showTip.value = false;
};
const operateClick = (e: any, item: tasks, index: number) => {
	if (e.index == 0) {
		editIndex.value = index;
		taskListSave.value = JSON.parse(JSON.stringify(taskList.value));
		taskList.value = [item];
		getPaths();
		isEditSingle.value = true;
		isEdit.value = true;
	} else {
		taskList.value.splice(index, 1);
	}
};
const cancelEditSingle = () => {
	taskListSave.value[editIndex.value] = taskList.value[0];
	taskList.value = JSON.parse(JSON.stringify(taskListSave.value));
	getPaths();
	nextTick(() => {
		isEdit.value = !isEdit.value;
		isEditSingle.value = false;
	});
};
const changeTypeVal = (index: number, Listindex: number) => {
	taskList.value[Listindex].type = state.typeList[index].value;
};
const changeMadeVal = (index: number, Listindex: number) => {
	taskList.value[Listindex].rub_type = state.modeList[index].value;
};
const changeSpeedVal = (index: number, Listindex: number) => {
	taskList.value[Listindex].max_speed = state.speedList[index].value;
};
const changeZoneType = (index: number, val: string) => {
	taskList.value[index].task_type = val;
	getPaths();
};
const confirmZone = (v) => {
	showZone.value = false;
	getPaths();
};
const confirmPath = (v) => {
	getPaths();
};
const getPaths = () => {
	const oldTasksList = JSON.parse(JSON.stringify(taskList.value)) as tasks[];
	const newTasksList: tasks[] = [];
	for (const task of oldTasksList) {
		if (task.task_type === "both1") {
			const arr1 = { ...task, task_type: "edge" };
			const arr2 = { ...task, task_type: "coverage" };
			newTasksList.push(arr1, arr2);
		} else if (task.task_type === "both2") {
			const arr1 = { ...task, task_type: "edge" };
			const arr2 = { ...task, task_type: "coverage" };
			newTasksList.push(arr2, arr1);
		} else {
			newTasksList.push(task);
		}
	}

	for (let i = 0; i < newTasksList.length; i++) {
		const task = newTasksList[i];
		let obj: ZoneDisplay = {
			url: "",
			x: 0,
			y: 0,
			path: "",
			type: "csv",
		};
		if (task.type === "zone" && task.zoneVal[0]) {
			const zone = state.defaultZone[0].find(
				(item) => item.id === task.zoneVal[0]
			);
			if (zone) {
				obj = {
					url: zone.zone_docs[0].oss_url,
					x: zone.rect[0],
					y: zone.rect[1],
					path: "",
					type: "csv",
				};

				const matchingDoc = zone.zone_docs.find((doc) =>
					doc.name.includes(task.task_type)
				);
				if (matchingDoc) {
					obj.path = matchingDoc.oss_url;
				}
			}
			zoneList.value[i] = obj;
		}
		if (task.type === "path" && task.pathVal[0]) {
			const path = state.defaultPath[0].find(
				(item) => item.id === task.pathVal[0]
			);
			if (path) {
				obj = {
					url: path.path_docs[0].oss_url,
					x: 0,
					y: 0,
					path: path.path_docs[0].oss_url,
					type: "csv",
				};
			}
			zoneList.value[i] = obj;
		}
	}
};
const addTaskFun = () => {
	taskList.value.push({
		type: "zone", //分区、路径
		zoneVal: [],
		pathVal: [],
		task_type: "edge", //沿边/覆盖
		rub_type: "huge", // 挡板强度
		max_speed: 0.7, //清扫速度
		light: false, //使能警示灯，默认false
		brush: true, //开启边刷
		task_times: 1, //循环次数
		isopens: false, //强沿边模式
		water: false, //开启喷雾
		patrol: false, //开启巡扫模式
		id: taskList.value.length + 1,
	});
};
const returnFun = () => {
	isEdit.value = true;
};
// 处理任务类型转换
const processTaskTypes = (tasks: tasks[]): tasks[] => {
	// 1. 先处理 path 类型的默认 task_type

	const tasksWithDefaults = tasks.map((task) => {
		const isPathType = task.type === "path";
		const zoneId =
			(!isPathType &&
				state.defaultZone[0]?.find(
					(item) => item.id === task.zoneVal[0]
				)?.zone_id) ||
			"";

		return {
			...task,
			zone_id: zoneId,
			path_id: isPathType ? task.pathVal[0] : "",
			task_type: isPathType ? "manual" : task.task_type,
		};
	});

	// 2. 展开 both1 和 both2 类型
	const expandedTasks: tasks[] = [];
	tasksWithDefaults.forEach((task) => {
		if (task.task_type === "both1") {
			expandedTasks.push(
				{ ...task, task_type: "edge" },
				{ ...task, task_type: "coverage" }
			);
		} else if (task.task_type === "both2") {
			expandedTasks.push(
				{ ...task, task_type: "coverage" },
				{ ...task, task_type: "edge" }
			);
		} else {
			expandedTasks.push(task);
		}
	});

	// 3. 处理 isopens 的特殊情况
	return expandedTasks.map((task) => {
		if (task.type === "path") {
			return {
				...task,
				task_type: task.isopens ? "strong_edge" : "manual",
			};
		}
		return task;
	});
};
const saveFun = async (type: number) => {
	// 检查是否有未设置的区域或路径
	const isInvalid = taskList.value.some((task) =>
		task.type === "zone" ? !task.zoneVal.length : !task.pathVal.length
	);
	if (taskList.value.length === 0 || isInvalid) {
		instance?.proxy.$message(t("plan.info.noSetArea"), "error");
		return;
	}
	if (type === 0) {
		isEdit.value = false;
	} else {
		showTip.value = true;
	}
};
defineExpose({
	saveFun,
});
const getDetail = () => {
	taskList.value =
		props.detailInfo?.tasks?.map((item: PathItem, index: number) => {
			const type =
				item.task_type === "manual" || item.task_type === "strong_edge"
					? "path"
					: "zone";
			const isPathType = type === "path";

			const zoneId = !isPathType
				? state.defaultZone[0]?.find(
						(zoneItem) => zoneItem.zone_id === item.zone_id
				  )?.id || ""
				: "";

			return {
				...item,
				type,
				id: index + 1,
				zoneVal: [zoneId],
				pathVal: [item.path_id],
			};
		}) || [];

	console.log(taskList.value);
	getPaths();
};
onMounted(() => {
	const mapStore: any = useUniversalStorage<string>("Map_Store", null);
	mapId.value = mapStore.value.map_info.map_id;
	state.defaultZone = [
		mapStore.value.zone_info.zones.map(
			(item: ZoneDisplay, index: number) => ({
				...item,
				id:
					item.zone_name +
					" 【" +
					t("addPlan.area") +
					"：" +
					item.area +
					"m²】",
			})
		),
	];
	state.defaultPath = [
		mapStore.value.path_infos.map((item: PathItem) => ({
			...item,
			id: item.path_id,
		})),
	];
	modelId.value = defaultDevice.value.model_id;
	deviceStore.selZone = [];
	if (hasDetailInfo.value) {
		getDetail();
	} else {
		addTaskFun();
		initialTaskList.value = cloneDeep(taskList.value);
	}
});
</script>

<style lang="scss" scoped>
:deep(.u-slide-up-enter-active) {
	/* #ifdef H5 */
	bottom: 0 !important;
	/* #endif */
}
:deep(.u-fade-enter-active) {
	/* #ifdef H5 */
	bottom: 0 !important;
	/* #endif */
}

.main {
	padding: 10rpx;
	/* #ifdef H5 */
	overflow: auto;
	/* #endif */
}
.map-box {
	width: 100%;
	background-color: #fff;
	padding: 10rpx;
	margin-bottom: 10rpx;
	box-sizing: border-box;
	border-radius: 20rpx;
	.map-content {
		background-color: #cdcdcd;
		margin-bottom: 10rpx;
		border-radius: 20rpx;
		height: 45vh;
		width: 100%;
		/* #ifdef APP-PLUS */
		overflow: hidden;
		/* #endif */
	}
}
.task-box {
	padding: 20rpx;
	background-color: #fff;
	display: flex;
	// padding-bottom: 0;
	align-items: center;
	flex-direction: column;
	box-sizing: border-box;
	.line-box {
		display: flex;
		justify-content: center;
		width: 100%;
		:deep(.u-line) {
			border-bottom: 1.2vh solid #d9d9d9 !important;
			border-radius: 10rpx;
		}
	}
	.tilte-box {
		width: calc(100% - 40rpx);
		border-radius: 20rpx 20rpx 0 0;
		background: linear-gradient(
			180deg,
			rgba(205, 224, 255, 0.56) 0%,
			#ffffff 100%
		);
		margin-top: 14rpx;
		padding: 20rpx 20rpx 20rpx 30rpx;
		display: flex;
		justify-content: space-between;
		align-items: center;
		.but {
			display: flex;
			gap: 16rpx;
		}
		.icon {
			position: relative;
			top: -6rpx;
		}
		:deep(.u-button--info) {
			border-color: #e8e8e8;
			height: 29px;
			line-height: 29px;
			color: #333;
		}
		.tip {
			padding: 10px;
			white-space: nowrap !important;
			display: inline-block;
			:deep(.u-text__value) {
				white-space: nowrap;
				overflow-wrap: nowrap;
			}
		}
	}
}
.task-list-com {
	display: flex;
	flex-direction: column;
	width: calc(100% - 40rpx);
	height: calc(45vh - 100px);
}
.drag-box {
	display: flex;
	flex-direction: column;
	min-height: calc(45vh - 100px);
	width: 100%;
	.drag-item {
		display: flex;
		justify-content: space-between;
		height: 49px;
		background-color: #fff;
		align-items: center;
		padding: 0 15px;
		border-bottom: 1px solid rgb(245, 246, 247);
	}
	:deep(.touch_move) {
		border: none !important;
	}
}

.task-list {
	display: flex;
	margin-top: 30rpx;
	gap: 20rpx;
	flex-direction: column;
	:deep(.u-picker-data) {
		border: 1px solid #dcdcdc;
		border-radius: 6rpx;
		padding: 10rpx 20rpx;
	}
	:deep(.u-input__content__field-wrapper__field) {
		line-height: 58rpx;
		font-size: 14px !important;
		color: rgba(102, 102, 102, 0.9) !important;
	}
	:deep(.uni-input-placeholder) {
		color: rgba(102, 102, 102, 0.9) !important;
	}
	.but-box {
		display: grid;
		grid-template-columns: repeat(3, 1fr);
		gap: 10px;
		justify-items: start;
		align-items: start;
		:deep(.u-button) {
			width: 100%;
			background-color: #f8f8f8;
			color: #000;
			border: 1px solid rgba(0, 0, 0, 0.2);
			border-radius: 5px;
			padding: 0;
			height: 31px;
			line-height: 31px;
			:deep(.u-button--active) {
				background-color: #007aff !important;
				color: #fff;
				box-shadow: none;
			}
			&:hover::before,
			&:hover::after {
				display: none !important;
				opacity: 0 !important;
				background: transparent !important;
			}
		}
		.active-but {
			background-color: #007aff;
			color: #fff;
		}
	}
	.open {
		display: inline-flex; /* 行内flex布局 */
		gap: 10px;
		align-items: center;
		:deep(.u-text) {
			display: inline !important;
			width: auto !important;
			flex: 0 1 auto !important;
		}
	}
	.num-box {
		:deep(.u-iconfont) {
			color: rgb(51, 51, 51) !important;
		}
		:deep(.u-number-box__minus .u-icon__icon) {
			font-size: 12rpx !important;
		}
		:deep(.u-number-box__plus .u-icon__icon) {
			font-size: 20rpx !important;
		}
		:deep(.u-number-box__minus--disabled .u-icon__icon) {
			color: #c0c0c0 !important;
		}
		:deep(.u-number-box__input),
		:deep(.cursor-pointer) {
			width: 51px !important;
			height: 29px;
			background: #ffffff !important;
			border: 1px solid #dcdcdc;
			border-radius: 4px !important;
		}
		:deep(.u-number-box__input) {
			margin: 0 5px;
		}
	}

	.line-bottm {
		margin-top: 30rpx !important;
		margin-bottom: 20rpx;
	}
	.open-edg {
		display: inline-flex;
	}
	.choseZone {
		:deep(.u-button) {
			justify-content: flex-start !important;
			text-align: left !important;
			color: rgba(102, 102, 102, 0.9);
			padding: 0 10px;
			border: 1px solid #dcdcdc;
		}
	}
}
.last-but {
	width: 100%;
	display: flex;
	justify-content: center;
	margin: 34rpx 0;
	:deep(.u-button) {
		max-width: 50%;
		height: 68rpx;
		border: 1px solid #707070;
		border-radius: 10rpx;
		line-height: 68rpx;
	}
	:deep(.u-button__text) {
		color: #666666;
		font-size: 16px !important;
	}
}
.content {
	text-align: center;
	display: flex;
	flex-direction: column;
	width: 100%;
	box-sizing: border-box;
	.title {
		padding: 8px 0 20px;
		text {
			font-size: 16px;
			font-weight: 500;
		}
		.blackTip {
			color: #909399;
		}
	}
	:deep(.u-input) {
		padding: 8px 9px !important;
	}
	:deep(.u-input__content__field-wrapper__field) {
		font-size: 14px !important;
	}
	:deep(.input-placeholder) {
		color: #555 !important;
	}
}
:deep(.u-popup__content),
:deep(.u-modal) {
	width: 300px !important;
}
:deep(.u-slide-up-enter-active) {
	/* #ifdef H5 */
	bottom: 0 !important;
	/* #endif */
}
:deep(.u-fade-enter-active) {
	/* #ifdef H5 */
	bottom: 0 !important;
	/* #endif */
}
:deep(.u-button--disabled) {
	opacity: 1 !important;
}
.my-component :deep([class*="u-button--disabled"]) {
	opacity: 1 !important;
}
:deep(.u-switch--disabled) {
	opacity: 1;
}
</style>
